package threading;

//阻塞队列 假定存储的元素是int
//基于数组来实现队列
class MyBlockingQueue{
    private int[] items = new int[1000];
    //约定 [head,tail) 队列的有效元素
    volatile private int head = 0;
    volatile private int tail = 0;
    volatile private int size = 0;

    //入队列
    synchronized public void put(int elem) throws InterruptedException {
        while(size == items.length){
            //队列满了，插入失败
            //return;
            this.wait();//满了 阻塞 等出队列唤醒
        }
        //把新元素放到 tail 所在位置上
        items[tail] = elem;
        tail++;
        //万一 tail 达到末尾 就需要让 tail 从头再来
//        if(tail == items.length){
//            tail = 0;
//        }
        tail = tail % items.length;
        size++;
        this.notify();//唤醒下面的 size=0
    }

    //出队列
    synchronized public Integer take() throws InterruptedException {
        while(size == 0){
            //return null;
            this.wait();//队列空就会阻塞 由入队列唤醒
        }
        int value = items[head];
        head++;
        if(head == items.length){
            head = 0;
        }
        size--;
        this.notify();//唤醒上面满的时候
        return value;

    }
}


public class ThreadDemo19 {
    public static void main(String[] args) {
        MyBlockingQueue queue = new MyBlockingQueue();
        //消费者
        Thread t1 = new Thread(()->{
            while(true){
                try {
                    int value = queue.take();
                    System.out.println("消费:"+value);
                    Thread.sleep(1000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        });
        //生产者
        Thread t2 = new Thread(()->{
            int value = 0;
            while(true){
                try {
                    System.out.println("生产:"+value);
                    queue.put(value);
                    value++;
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        });
        t1.start();
        t2.start();

    }
}
